package com.ideal.frame.institutions.service;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.date.DatePattern;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.io.FileUtil;
import cn.hutool.core.io.resource.ResourceUtil;
import cn.hutool.core.lang.Assert;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.RandomUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.core.util.XmlUtil;
import com.ideal.frame.common.enumerate.IdTypeEnum;
import com.ideal.frame.common.enumerate.OperTypeEnum;
import com.ideal.frame.common.enumerate.PlatformTypeEnums;
import com.ideal.frame.config.SFtpProperties;
import com.ideal.frame.institutions.dto.*;
import com.ideal.frame.institutions.entity.InstitutionsOrganizationTb;
import com.ideal.frame.institutions.entity.QInstitutionsOrganizationTb;
import com.ideal.frame.jpa.DSLPageRequest;
import com.ideal.frame.jpa.DSLRequest;
import com.ideal.frame.jpa.JpaRepositoryImpl;
import com.ideal.frame.node.entity.NodeTb;
import com.ideal.frame.node.netty.CurrentNode;
import com.ideal.frame.node.service.NodeService;
import com.ideal.frame.prefix.entity.PrefixSelfTb;
import com.ideal.frame.prefix.service.PrefixSelfTbService;
import com.ideal.frame.sys.dto.UserDto;
import com.ideal.frame.sys.form.search.OrganizationSearchForm;
import com.ideal.frame.util.SFtpUtil;
import com.ideal.frame.util.UserUtils;
import com.ideal.frame.util.XmlUtils;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.domain.Page;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.w3c.dom.Document;
import org.w3c.dom.Element;

import javax.annotation.PostConstruct;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import java.io.File;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Optional;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

@Slf4j
@Service
public class InstitutionsOrganizationService {
    @Value("${xmlPath}")
    String xmlPath;
    @Value("${tarPath}")
    String tarPath;
    @Value("${xsdPath}")
    String xsdPath;
    @PersistenceContext
    protected EntityManager entityManager;
    private JpaRepositoryImpl<InstitutionsOrganizationTb, String> ioRepo;

    QInstitutionsOrganizationTb qInstitutionsOrganizationTb = QInstitutionsOrganizationTb.institutionsOrganizationTb;

    @PostConstruct
    public void initRepo() {
        ioRepo = new JpaRepositoryImpl<>(InstitutionsOrganizationTb.class, entityManager);
    }

    @Autowired
    private InstitutionsIdregdatalistService idregdatalistService;
    @Autowired
    private InstitutionsIdsysbacklistService idsysbacklistService;
    @Autowired
    private InstitutionsIdregsyslistService idregsyslistService;
    @Autowired
    private InstitutionsLicencelistService licencelistService;
    @Autowired
    private InstitutionsRegdatabacklistService regdatabacklistService;
    @Autowired
    private InstitutionsRegservlistService regservlistService;
    @Autowired
    private InstitutionsServindustryService servindustryService;
    @Autowired
    private InstitutionsServsysbuildService servsysbuildService;
    @Autowired
    private InstitutionsServsysoperService servsysoperService;
    @Autowired
    private InstitutionsRegRealNalmpService regRealNalmpService;
    @Autowired
    private PrefixSelfTbService prefixSelfTbService;
    @Autowired
    private CurrentNode currentNode;
    @Autowired
    private RedisTemplate redisTemplate;
    @Autowired
    private NodeService nodeService;
    @Autowired
    private SFtpProperties sFtpProperties;


    @Transactional(rollbackFor = Exception.class)
    public void saveOrganizationInfo(OrganizationInfoDto organizationInfoDto) {
        InstitutionsOrganizationDto institutionsOrganizationDto = organizationInfoDto.getInstitutionsOrganizationTb();
        Assert.isTrue(institutionsOrganizationDto != null || !BeanUtil.isEmpty(institutionsOrganizationDto), "机构信息不能为空");
        String gnrlid = institutionsOrganizationDto.getGnrlid();
        Assert.isTrue(StrUtil.isNotBlank(gnrlid), "机构id不能为空");
        DSLRequest request = new DSLRequest();
        request.addWhere(qInstitutionsOrganizationTb.gnrlid.eq(gnrlid));
        request.addWhere(qInstitutionsOrganizationTb.delFlag.isFalse());
        List<InstitutionsOrganizationTb> all = ioRepo.findAll(request);
        Assert.isTrue(CollUtil.isEmpty(all), "机构id重复，请重新填写！");
        InstitutionsOrganizationTb institutionsOrganizationTb = new InstitutionsOrganizationTb();
        BeanUtil.copyProperties(institutionsOrganizationDto, institutionsOrganizationTb);
        institutionsOrganizationTb.setCreateTime(new Date());
        institutionsOrganizationTb.setCreateUser(UserUtils.getCurrentUser().getId());
        institutionsOrganizationTb.setDelFlag(false);
        UserDto userDto = UserUtils.getCurrentUser();
        String key = "virtual_node：" + userDto.getId();
        Object virtual = redisTemplate.opsForValue().get(key);
        if (virtual != null) {
            Long nodeId = (Long) virtual;
            NodeTb nodeTb = nodeService.getById(nodeId);
            Assert.isTrue(nodeTb != null , "节点已删除！");
            Assert.isTrue(ObjectUtil.equal(nodeTb.getNodetype(), 2), "节点不是虚节点！");
            // 虚节点
            institutionsOrganizationTb.setBelongNodeId(nodeId);
        } else {
            // 为空表示选择的是yml中配置的节点
            institutionsOrganizationTb.setBelongNodeId(currentNode.getId());
        }
        ioRepo.save(institutionsOrganizationTb);

        idregdatalistService.save(organizationInfoDto.getInstitutionsIdregdatalistTbs(), gnrlid);
        idsysbacklistService.save(organizationInfoDto.getInstitutionsIdsysbacklistTbs(), gnrlid);
        idregsyslistService.save(organizationInfoDto.getInstitutionsIdregsyslistTbs(), gnrlid);
        licencelistService.save(organizationInfoDto.getInstitutionsLicencelistTbs(), gnrlid);
//        if (organizationInfoDto.getInstitutionsLicencelistTb() != null && !BeanUtil.isEmpty(organizationInfoDto.getInstitutionsLicencelistTb())) {
//            licencelistService.save(organizationInfoDto.getInstitutionsLicencelistTb().setGnrlid(gnrlid));
//        }
        regdatabacklistService.save(organizationInfoDto.getInstitutionsRegdatabacklistTbs(), gnrlid);
        regservlistService.save(organizationInfoDto.getInstitutionsRegservlistTbs(), gnrlid);
        if (organizationInfoDto.getInstitutionsServindustryTb() != null && !BeanUtil.isEmpty(organizationInfoDto.getInstitutionsServindustryTb())) {
            servindustryService.save(organizationInfoDto.getInstitutionsServindustryTb().setGnrlid(gnrlid));
        }
        if (organizationInfoDto.getInstitutionsServsysbuildTb() != null && !BeanUtil.isEmpty(organizationInfoDto.getInstitutionsServsysbuildTb())) {
            servsysbuildService.save(organizationInfoDto.getInstitutionsServsysbuildTb().setGnrlid(gnrlid));
        }
        if (organizationInfoDto.getInstitutionsServsysoperTb() != null && !BeanUtil.isEmpty(organizationInfoDto.getInstitutionsServsysoperTb())) {
            servsysoperService.save(organizationInfoDto.getInstitutionsServsysoperTb().setGnrlid(gnrlid));
        }
        if (organizationInfoDto.getInstitutionsRegRealNalmpTb() != null && !BeanUtil.isEmpty(organizationInfoDto.getInstitutionsRegRealNalmpTb())) {
            regRealNalmpService.save(organizationInfoDto.getInstitutionsRegRealNalmpTb().setGnrlid(gnrlid));
        }
    }

    public InstitutionsOrganizationDto getOrganizationInfo(String gnrlid) {
        Optional<InstitutionsOrganizationTb> tb = ioRepo.findOne(qInstitutionsOrganizationTb.gnrlid.eq(gnrlid)
                .and(qInstitutionsOrganizationTb.delFlag.isFalse()));
        InstitutionsOrganizationDto institutionsOrganizationDto = new InstitutionsOrganizationDto();
        tb.ifPresent(institutionsOrganizationTb -> BeanUtil.copyProperties(institutionsOrganizationTb, institutionsOrganizationDto));
        return institutionsOrganizationDto;
    }

    @Transactional(rollbackFor = Exception.class)
    public void deleteOrganization(String gnrlid) {
        ioRepo.update(qInstitutionsOrganizationTb).set(qInstitutionsOrganizationTb.delFlag, true)
                .where(qInstitutionsOrganizationTb.gnrlid.eq(gnrlid)).execute();
        idregdatalistService.deleteById(gnrlid);
        idsysbacklistService.deleteById(gnrlid);
        idregsyslistService.deleteById(gnrlid);
        licencelistService.deleteById(gnrlid);
        regdatabacklistService.deleteById(gnrlid);
        regservlistService.deleteById(gnrlid);
        servindustryService.deleteById(gnrlid);
        servsysbuildService.deleteById(gnrlid);
        servsysoperService.deleteById(gnrlid);
    }

    public Page<InstitutionsOrganizationTb> getPage(OrganizationSearchForm searchForm) {
        DSLPageRequest pageRequest = searchForm.asDslPageRequest();
        if (StringUtils.isNotEmpty(searchForm.getGnrlId())) {
            pageRequest.addWhere(qInstitutionsOrganizationTb.gnrlid.eq(searchForm.getGnrlId()));
        }
        if (StringUtils.isNotEmpty(searchForm.getOrgName())) {
            pageRequest.addWhere(qInstitutionsOrganizationTb.orgname.like("%" + searchForm.getOrgName() + "%"));
        }
        pageRequest.addWhere(qInstitutionsOrganizationTb.belongNodeId.eq(getNodeId()));
        pageRequest.addWhere(qInstitutionsOrganizationTb.delFlag.isFalse());
        return ioRepo.findAll(pageRequest);
    }

    public List<InstitutionsOrganizationTb> getAll(){
        return ioRepo.findAll(qInstitutionsOrganizationTb.delFlag.isFalse()
                .and(qInstitutionsOrganizationTb.rootNodeId.isNull())
                .and(qInstitutionsOrganizationTb.belongNodeId.eq(getNodeId())));
    }

    /**
     * 查询没有绑定的根节点和前缀的机构
     * @return
     */
    public List<InstitutionsOrganizationTb> getNotBindOrg(){
        return ioRepo.findAll(qInstitutionsOrganizationTb.delFlag.isFalse()
                .and(qInstitutionsOrganizationTb.prefix.isNull()));
    }

    @Transactional(rollbackFor = Exception.class)
    public void editOrganizationInfo(OrganizationInfoDto organizationInfoDto) {
        InstitutionsOrganizationDto institutionsOrganizationDto = organizationInfoDto.getInstitutionsOrganizationTb();
        Assert.isTrue(institutionsOrganizationDto != null, "参数不能为空!");
        Long id = institutionsOrganizationDto.getId();
        Optional<InstitutionsOrganizationTb> optional = ioRepo.findOne(qInstitutionsOrganizationTb.id.eq(id)
                .and(qInstitutionsOrganizationTb.delFlag.isFalse()));
        Assert.isTrue(optional.isPresent(), "数据不存在，无法编辑！");
        String gnrlid = institutionsOrganizationDto.getGnrlid();
        Assert.isTrue(gnrlid != null, "机构id不能为空");
        Optional<InstitutionsOrganizationTb> optional1 = ioRepo.findOne(qInstitutionsOrganizationTb.gnrlid.eq(gnrlid)
                .and(qInstitutionsOrganizationTb.id.ne(id))
                .and(qInstitutionsOrganizationTb.delFlag.isFalse()));
        Assert.isTrue(!optional1.isPresent(), "机构id重复无法修改");
        InstitutionsOrganizationTb institutionsOrganizationTb = optional.get();
        BeanUtil.copyProperties(institutionsOrganizationDto, institutionsOrganizationTb);
        institutionsOrganizationTb.setModifyTime(new Date());
        institutionsOrganizationTb.setModifyUser(UserUtils.getCurrentUser().getId());
        ioRepo.save(institutionsOrganizationTb);
        idregdatalistService.edit(organizationInfoDto.getInstitutionsIdregdatalistTbs(), gnrlid);
        idsysbacklistService.edit(organizationInfoDto.getInstitutionsIdsysbacklistTbs(), gnrlid);
        idregsyslistService.edit(organizationInfoDto.getInstitutionsIdregsyslistTbs(), gnrlid);
        regdatabacklistService.edit(organizationInfoDto.getInstitutionsRegdatabacklistTbs(), gnrlid);
        regservlistService.edit(organizationInfoDto.getInstitutionsRegservlistTbs(), gnrlid);
        licencelistService.edit(organizationInfoDto.getInstitutionsLicencelistTbs(), gnrlid);
//        if (organizationInfoDto.getInstitutionsLicencelistTb() != null && !BeanUtil.isEmpty(organizationInfoDto.getInstitutionsLicencelistTb())) {
//            licencelistService.save(organizationInfoDto.getInstitutionsLicencelistTb().setGnrlid(gnrlid));
//        }
        if (organizationInfoDto.getInstitutionsServindustryTb() != null && !BeanUtil.isEmpty(organizationInfoDto.getInstitutionsServindustryTb())) {
            servindustryService.save(organizationInfoDto.getInstitutionsServindustryTb().setGnrlid(gnrlid));
        }
        if (organizationInfoDto.getInstitutionsServsysbuildTb() != null && !BeanUtil.isEmpty(organizationInfoDto.getInstitutionsServsysbuildTb())) {
            servsysbuildService.save(organizationInfoDto.getInstitutionsServsysbuildTb().setGnrlid(gnrlid));
        }
        if (organizationInfoDto.getInstitutionsServsysoperTb() != null && !BeanUtil.isEmpty(organizationInfoDto.getInstitutionsServsysoperTb())) {
            servsysoperService.save(organizationInfoDto.getInstitutionsServsysoperTb().setGnrlid(gnrlid));
        }
        if (organizationInfoDto.getInstitutionsRegRealNalmpTb() != null && !BeanUtil.isEmpty(organizationInfoDto.getInstitutionsRegRealNalmpTb())) {
            regRealNalmpService.save(organizationInfoDto.getInstitutionsRegRealNalmpTb().setGnrlid(gnrlid));
        }
    }

    public long registerOrganizationCount() {
        return ioRepo.count(qInstitutionsOrganizationTb.delFlag.isFalse().and(qInstitutionsOrganizationTb.belongNodeId.eq(getNodeId())));
    }

    public List<MainOrganizationDto> listMainOrganization() {
        List<MainOrganizationDto> list = new ArrayList<>();
        // 2级节点
        if (currentNode.getLevel() == 2) {
            String sql = "SELECT DISTINCT(iot.gnrlId) gnrlid, iot.id org_id, iot.orgName, nt.nodename, nt.nodeip, nt.nodelevel, nt.prefix_id, " +
                    "nt.id node_id FROM node_tb nt LEFT JOIN prefix_netx_tb pnt ON nt.prefix_id = pnt.id " +
                    "LEFT JOIN institutions_organization_tb iot ON pnt.gnrlId = iot.id WHERE nt.isdelete = 0 " +
                    "AND pnt.isdelete = 0 AND iot.del_flag = 0 and nt.nodetype = 2";
            MainOrganizationDto mainOrganizationDto = new MainOrganizationDto();
            mainOrganizationDto.setNodeId(currentNode.getId());
            mainOrganizationDto.setNodeip(currentNode.getIp());
            mainOrganizationDto.setNodename(currentNode.getName());
            mainOrganizationDto.setNodelevel(currentNode.getLevel());
            mainOrganizationDto.setNodetype(currentNode.getType());
            PrefixSelfTb currentPrefixSelf = prefixSelfTbService.getCurrentPrefixSelf();
            mainOrganizationDto.setPrefix(currentPrefixSelf.getPrefixSelf());
//            InstitutionsOrganizationTb institutionsOrganizationTb = ioRepo.selectFrom(qInstitutionsOrganizationTb).where(qInstitutionsOrganizationTb.prefix.eq(currentPrefixSelf.getPrefixSelf())).fetchFirst();
//            if (institutionsOrganizationTb != null) {
//                mainOrganizationDto.setOrgname(institutionsOrganizationTb.getOrgname());
//                mainOrganizationDto.setOrgId(institutionsOrganizationTb.getId());
//                mainOrganizationDto.setGnrlid(institutionsOrganizationTb.getGnrlid());
//            }
            mainOrganizationDto.setOrgname("本级机构");
            mainOrganizationDto.setOrgId(-1L);
            list.add(mainOrganizationDto);
            list.addAll(ioRepo.selectByNativeQuery(sql, new ArrayList<>(), MainOrganizationDto.class));
        }
        return list;
    }

    public Long getNodeId() {
        UserDto userDto = UserUtils.getCurrentUser();
        String key = "virtual_node：" + userDto.getId();
        Object virtual = redisTemplate.opsForValue().get(key);
        long nodeId = currentNode.getId();
        if (virtual != null) {
            nodeId = (Long) virtual;
        }
        return nodeId;
    }

    public void xml() {
        Date date = new Date();
        String timePath = DateUtil.format(date, DatePattern.PURE_DATE_FORMAT) + "/" + DateUtil.hour(date, true) + "/";
        // 保证每步串行执行
        ExecutorService executorService = Executors.newSingleThreadExecutor();
        executorService.execute(() -> createXml(timePath));
        executorService.execute(() -> validateXML(timePath));
        executorService.execute(() -> packetOrgXml(timePath));
        executorService.execute(() -> uploadOrgXml(timePath));
        executorService.shutdown();
    }

    /**
     * 创建
     */
    @Transactional(rollbackFor = Exception.class)
    public void createXml(String timePath) {
        log.info("**********************创建xml开始***********************");
        long currentTimeMillis = DateUtil.current(false);
        Date now = new Date(currentTimeMillis);
        String startTime = DateUtil.format(DateUtil.offsetHour(now, -1), "yyyy-MM-dd HH") + ":00:00";
        String endTime = DateUtil.format(now, "yyyy-MM-dd HH") + ":00:00";
        List<InstitutionsOrganizationTb> all = ioRepo.findAll(qInstitutionsOrganizationTb.delFlag.isFalse()
                .and(qInstitutionsOrganizationTb.createTime.goe(DateUtil.parse(startTime)))
                .and(qInstitutionsOrganizationTb.createTime.lt(DateUtil.parse(endTime)))
                .and(qInstitutionsOrganizationTb.prefix.isNotNull()));
        Document document;
        if (CollUtil.isEmpty(all)) {
            // 创建document
            document = XmlUtil.createXml();
            // 公共部分
            Element root = commonElement(currentTimeMillis, now, document);

            // 无上报数据
            Element noDataElement = document.createElement("rsmi:noData");
            Element describeElement = document.createElement("bt:describe");
            describeElement.setTextContent("无数据说明");
            noDataElement.appendChild(describeElement);
            root.appendChild(noDataElement);

            // 写入到xml
            writeXml(document, now, root, timePath);
        } else {
            // 有上报数据
            for (InstitutionsOrganizationTb institutionsOrganizationTb : all) {
                currentTimeMillis = DateUtil.current(false);
                now = new Date(currentTimeMillis);
                // 创建document
                document = XmlUtil.createXml();
                // 公共部分
                Element root = commonElement(currentTimeMillis, now, document);
                // 设置机构信息
                Element dataElement = setDataElement(document, institutionsOrganizationTb);
                // 添加到根节点
                root.appendChild(dataElement);
                // 写入到xml
                writeXml(document, now, root, timePath);
            }
        }
        log.info("**********************创建xml结束***********************");
    }

    private Element commonElement(long currentTimeMillis, Date now, Document document) {
        Element root = document.createElement("rsmi:regSrvMainInfo");

        root.setAttribute("xmlns:rsmi", "urn:ietf:params:xml:ns:regsvrmaininfo-1.0");
        root.setAttribute("xmlns:bt", "urn:ietf:params:xml:ns:basetype-1.0");
        root.setAttribute("xmlns:rmci", "urn:ietf:params:xml:ns:regmancominfo-1.0");

        Element pubKeySignElement = document.createElement("rsmi:pubKeySign");
        pubKeySignElement.setTextContent(" ");
        root.appendChild(pubKeySignElement);

        Element regManComInfoElement = document.createElement("rsmi:regManComInfo");
        root.appendChild(regManComInfoElement);

        Element regServerTypeElement = document.createElement("rmci:regServerType");
        regManComInfoElement.appendChild(regServerTypeElement);

        Element servNameElement = document.createElement("bt:servName");
        servNameElement.setTextContent(currentNode.getServName());
        regServerTypeElement.appendChild(servNameElement);

        Element gnrlIdElement = document.createElement("bt:gnrlId");
        gnrlIdElement.setTextContent(currentNode.getGnrlId());
        regServerTypeElement.appendChild(gnrlIdElement);

        Element idTypeElement = document.createElement("rmci:idType");
        idTypeElement.setTextContent(IdTypeEnum.HANDLE.getText());
        regManComInfoElement.appendChild(idTypeElement);

        Element dataCrtTimeElement = document.createElement("rmci:dataCrtTime");
        dataCrtTimeElement.setTextContent(DateUtil.format(now, DatePattern.UTC_MS_FORMAT));
        regManComInfoElement.appendChild(dataCrtTimeElement);

        Element operTypeElement = document.createElement("rmci:operType");
        operTypeElement.setTextContent(OperTypeEnum.CREATE.getText());
        regManComInfoElement.appendChild(operTypeElement);

        Element transIdElement = document.createElement("rmci:transId");
        transIdElement.setTextContent(String.valueOf(currentTimeMillis));
        regManComInfoElement.appendChild(transIdElement);
        return root;
    }

    private Element setDataElement(Document document, InstitutionsOrganizationTb institutionsOrganizationTb) {
        Element dataElement = document.createElement("rsmi:data");

        String gnrlid = institutionsOrganizationTb.getGnrlid();
        Element gnriIdElement = document.createElement("rsmi:gnrlId");
        gnriIdElement.setTextContent(gnrlid);
        dataElement.appendChild(gnriIdElement);

        if (institutionsOrganizationTb.getPrefix() != null) {
            Element prefixElement = document.createElement("rsmi:prefix");
            prefixElement.setTextContent(institutionsOrganizationTb.getPrefix());
            dataElement.appendChild(prefixElement);
        }
        if (institutionsOrganizationTb.getOrgname() != null) {
            Element orgNameElement = document.createElement("rsmi:orgName");
            orgNameElement.setTextContent(institutionsOrganizationTb.getOrgname());
            dataElement.appendChild(orgNameElement);
        }
        if (institutionsOrganizationTb.getOrgnature() != null) {
            Element orgNatureElement = document.createElement("rsmi:orgNature");
            orgNatureElement.setTextContent(String.valueOf(institutionsOrganizationTb.getOrgnature()));
            dataElement.appendChild(orgNatureElement);
        }
        if (institutionsOrganizationTb.getOrgaddr() != null) {
            Element orgAddrElement = document.createElement("rsmi:orgAddr");
            orgAddrElement.setTextContent(institutionsOrganizationTb.getOrgaddr());
            dataElement.appendChild(orgAddrElement);
        }
        if (institutionsOrganizationTb.getOrgaddrcity() != null) {
            Element element = document.createElement("rsmi:orgAddrCity");
            element.setTextContent(institutionsOrganizationTb.getOrgaddrcity());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getOrgaddrcounty() != null) {
            Element element = document.createElement("rsmi:orgAddrCounty");
            element.setTextContent(institutionsOrganizationTb.getOrgaddrcounty());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getOrgaddrprovince() != null) {
            Element element = document.createElement("rsmi:orgAddrProvince");
            element.setTextContent(institutionsOrganizationTb.getOrgaddrprovince());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getOrgcrttype() != null) {
            Element element = document.createElement("rsmi:orgCrtType");
            element.setTextContent(institutionsOrganizationTb.getOrgcrttype());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getOrgcrtcode() != null) {
            Element element = document.createElement("rsmi:orgCrtCode");
            element.setTextContent(institutionsOrganizationTb.getOrgcrtcode());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getLegalname() != null) {
            Element element = document.createElement("rsmi:legalName");
            element.setTextContent(institutionsOrganizationTb.getLegalname());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getLegalcrttype() != null) {
            Element element = document.createElement("rsmi:legalCrtType");
            element.setTextContent(String.valueOf(institutionsOrganizationTb.getLegalcrttype()));
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getLegalcrtno() != null) {
            Element element = document.createElement("rsmi:legalCrtNo");
            element.setTextContent(institutionsOrganizationTb.getLegalcrtno());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getOrgdesc() != null) {
            Element element = document.createElement("rsmi:orgDesc");
            element.setTextContent(institutionsOrganizationTb.getOrgdesc());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getIndustrycategory() != null) {
            Element element = document.createElement("rsmi:industryCategory");
            element.setTextContent(institutionsOrganizationTb.getIndustrycategory());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getIndustryspecific() != null) {
            Element element = document.createElement("rsmi:industrySpecific");
            element.setTextContent(institutionsOrganizationTb.getIndustryspecific());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getContactname() != null) {
            Element element = document.createElement("rsmi:contactName");
            element.setTextContent(institutionsOrganizationTb.getContactname());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getContactphone() != null) {
            Element element = document.createElement("rsmi:contactPhone");
            element.setTextContent(institutionsOrganizationTb.getContactphone());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getContactcrttype() != null) {
            Element element = document.createElement("rsmi:contactCrtType");
            element.setTextContent(institutionsOrganizationTb.getContactcrttype());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getContactcrtno() != null) {
            Element element = document.createElement("rsmi:contactCrtNo");
            element.setTextContent(institutionsOrganizationTb.getContactcrtno());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getContactemail() != null) {
            Element element = document.createElement("rsmi:contactEmail");
            element.setTextContent(institutionsOrganizationTb.getContactemail());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getWebsite() != null) {
            Element element = document.createElement("rsmi:website");
            element.setTextContent(institutionsOrganizationTb.getWebsite());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getRegauthority() != null) {
            Element element = document.createElement("rsmi:regAuthority");
            element.setTextContent(institutionsOrganizationTb.getRegauthority());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getRegcapital() != null) {
            Element element = document.createElement("rsmi:regCapital");
            element.setTextContent(institutionsOrganizationTb.getRegcapital());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getEstablishdate() != null) {
            Element element = document.createElement("rsmi:establishDate");
            element.setTextContent(institutionsOrganizationTb.getEstablishdate());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getPeriodvalidity() != null) {
            Element element = document.createElement("rsmi:periodValidity");
            element.setTextContent(institutionsOrganizationTb.getPeriodvalidity());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getLegalphone() != null) {
            Element element = document.createElement("rsmi:legalPhone");
            element.setTextContent(institutionsOrganizationTb.getLegalphone());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getLegalemail() != null) {
            Element element = document.createElement("rsmi:legalEmail");
            element.setTextContent(institutionsOrganizationTb.getLegalemail());
            dataElement.appendChild(element);
        }
        if (institutionsOrganizationTb.getLegalfax() != null) {
            Element element = document.createElement("rsmi:legalFax");
            element.setTextContent(institutionsOrganizationTb.getLegalfax());
            dataElement.appendChild(element);
        }

        regservlistXml(document, dataElement, gnrlid);
        regDataBackListXml(document, dataElement, gnrlid);
        idsysbacklistXml(document, dataElement, gnrlid);
        idregsyslistXml(document, dataElement, gnrlid);
        idregdatalistXml(document, dataElement, gnrlid);

        List<InstitutionsLicencelistDto> licencelistDtos = licencelistService.getByGnrlid(gnrlid);
        if (CollUtil.isNotEmpty(licencelistDtos)) {
            Element element = document.createElement("rsmi:licenceList");
            for (InstitutionsLicencelistDto licencelistDto : licencelistDtos) {
                Element element1 = document.createElement("bt:licence");
                element1.setAttribute("licenceType", licencelistDto.getLicencetype());
                element1.setAttribute("licenceNo", licencelistDto.getLicenceno());
                element.appendChild(element1);
            }
            dataElement.appendChild(element);
        }
//        if (!BeanUtil.isEmpty(licencelistDto)) {
//            Element element = document.createElement("rsmi:licenceList");
//            Element element1 = document.createElement("bt:licence");
//            element1.setAttribute("licenceType", licencelistDto.getLicencetype());
//            element1.setAttribute("licenceNo", licencelistDto.getLicenceno());
//            element.appendChild(element1);
//            dataElement.appendChild(element);
//        }
        InstitutionsServindustryDto servindustryDto = servindustryService.getByGnrlid(gnrlid);
        if (!BeanUtil.isEmpty(servindustryDto)) {
            Element element = document.createElement("rsmi:servIndustry");
            Element element1 = document.createElement("bt:industry");
            element1.setAttribute("category", servindustryDto.getCategory());
            element1.setAttribute("specific", servindustryDto.getSpecific());
            element1.setAttribute("trade", servindustryDto.getTrade());
            element1.setAttribute("subclass", servindustryDto.getSubclass());
            element.appendChild(element1);
            dataElement.appendChild(element);
        }
        InstitutionsServsysbuildDto servsysbuildDto = servsysbuildService.getByGnrlid(gnrlid);
        if (!BeanUtil.isEmpty(servsysbuildDto)) {
            Element element = document.createElement("rsmi:servSysBuild");
            element.setAttribute("biudType", String.valueOf(servsysbuildDto.getBiudtype()));
            element.setAttribute("entrOrg", servsysbuildDto.getEntrorg());
            dataElement.appendChild(element);
        }
        InstitutionsServsysoperDto servsysoperDto = servsysoperService.getByGnrlid(gnrlid);
        if (!BeanUtil.isEmpty(servsysoperDto)) {
            Element element = document.createElement("rsmi:servSysOper");
            element.setAttribute("biudType", String.valueOf(servsysoperDto.getBiudtype()));
            element.setAttribute("entrOrg", servsysoperDto.getEntrorg());
            dataElement.appendChild(element);
        }
        InstitutionsRegRealNalmpDto regRealNalmpDto = regRealNalmpService.getByGnrlid(gnrlid);
        if (!BeanUtil.isEmpty(regRealNalmpDto)) {
            Element element = document.createElement("rsmi:regRealNaImp");
            element.setAttribute("biudType", String.valueOf(regRealNalmpDto.getBiudtype()));
            element.setAttribute("entrOrg", regRealNalmpDto.getEntrorg());
            dataElement.appendChild(element);
        }
        return dataElement;
    }

    private void regservlistXml(Document document, Element dataElement, String gnrlid) {
        List<InstitutionsRegservlistDto> list = regservlistService.getByGnrlid(gnrlid);
        if (CollUtil.isNotEmpty(list)) {
            Element element = document.createElement("rsmi:resServList");
            for (InstitutionsRegservlistDto v : list) {
                Element element1 = document.createElement("rsmi:resServInfo");
                if (v.getDeploymode() != null) {
                    Element element2 = document.createElement("bt:deployMode");
                    element2.setTextContent(String.valueOf(v.getDeploymode()));
                    element1.appendChild(element2);
                }
                if (v.getName() != null) {
                    Element element2 = document.createElement("bt:name");
                    element2.setTextContent(String.valueOf(v.getName()));
                    element1.appendChild(element2);
                }
                if (v.getAddress() != null) {
                    Element element2 = document.createElement("bt:deployInfo");
                    element2.setAttribute("addrss", v.getAddress());
                    element2.setAttribute("city", v.getCity());
                    element2.setAttribute("county", v.getCounty());
                    element2.setAttribute("province", v.getProvince());
                    element1.appendChild(element2);
                }
                element.appendChild(element1);
            }
            dataElement.appendChild(element);
        }
    }

    private void regDataBackListXml(Document document, Element dataElement, String gnrlid) {
        List<InstitutionsRegdatabacklistDto> list = regdatabacklistService.getByGnrlid(gnrlid);
        if (CollUtil.isNotEmpty(list)) {
            Element element = document.createElement("rsmi:regDataBackList");
            for (InstitutionsRegdatabacklistDto v : list) {
                Element element1 = document.createElement("rsmi:regDataBackInfo");
                if (v.getDeploymode() != null) {
                    Element element2 = document.createElement("bt:deployMode");
                    element2.setTextContent(String.valueOf(v.getDeploymode()));
                    element1.appendChild(element2);
                }
                if (v.getName() != null) {
                    Element element2 = document.createElement("bt:name");
                    element2.setTextContent(String.valueOf(v.getName()));
                    element1.appendChild(element2);
                }
                if (v.getAddress() != null) {
                    Element element2 = document.createElement("bt:deployInfo");
                    element2.setAttribute("addrss", v.getAddress());
                    element2.setAttribute("city", v.getCity());
                    element2.setAttribute("county", v.getCounty());
                    element2.setAttribute("province", v.getProvince());
                    element1.appendChild(element2);
                }
                element.appendChild(element1);
            }
            dataElement.appendChild(element);
        }
    }

    private void idsysbacklistXml(Document document, Element dataElement, String gnrlid) {
        List<InstitutionsIdsysbacklistDto> list = idsysbacklistService.getByGnrlid(gnrlid);
        if (CollUtil.isNotEmpty(list)) {
            Element element = document.createElement("rsmi:idSysBackList");
            for (InstitutionsIdsysbacklistDto v : list) {
                Element element1 = document.createElement("rsmi:idSysBackInfo");
                if (v.getDeploymode() != null) {
                    Element element2 = document.createElement("bt:deployMode");
                    element2.setTextContent(String.valueOf(v.getDeploymode()));
                    element1.appendChild(element2);
                }
                if (v.getName() != null) {
                    Element element2 = document.createElement("bt:name");
                    element2.setTextContent(String.valueOf(v.getName()));
                    element1.appendChild(element2);
                }
                if (v.getAddress() != null) {
                    Element element2 = document.createElement("bt:deployInfo");
                    element2.setAttribute("addrss", v.getAddress());
                    element2.setAttribute("city", v.getCity());
                    element2.setAttribute("county", v.getCounty());
                    element2.setAttribute("province", v.getProvince());
                    element1.appendChild(element2);
                }
                element.appendChild(element1);
            }
            dataElement.appendChild(element);
        }
    }

    private void idregsyslistXml(Document document, Element dataElement, String gnrlid) {
        List<InstitutionsIdregsyslistDto> idregsyslistDtos = idregsyslistService.getByGnrlid(gnrlid);
        if (CollUtil.isNotEmpty(idregsyslistDtos)) {
            Element element = document.createElement("rsmi:idRegSysList");
            for (InstitutionsIdregsyslistDto v : idregsyslistDtos) {
                Element idRegSysInfoElement = document.createElement("rsmi:idRegSysInfo");
                if (v.getDeploymode() != null) {
                    Element deployModeElement = document.createElement("bt:deployMode");
                    deployModeElement.setTextContent(String.valueOf(v.getDeploymode()));
                    idRegSysInfoElement.appendChild(deployModeElement);
                }
                if (v.getName() != null) {
                    Element nameElement = document.createElement("bt:name");
                    nameElement.setTextContent(String.valueOf(v.getName()));
                    idRegSysInfoElement.appendChild(nameElement);
                }
                if (v.getAddress() != null) {
                    Element deployInfoElement = document.createElement("bt:deployInfo");
                    deployInfoElement.setAttribute("addrss", v.getAddress());
                    deployInfoElement.setAttribute("city", v.getCity());
                    deployInfoElement.setAttribute("county", v.getCounty());
                    deployInfoElement.setAttribute("province", v.getProvince());
                    idRegSysInfoElement.appendChild(deployInfoElement);
                }
                element.appendChild(idRegSysInfoElement);
            }
            dataElement.appendChild(element);
        }
    }

    private void idregdatalistXml(Document document, Element dataElement, String gnrlid) {
        List<InstitutionsIdregdatalistDto> idregdatalistDtos = idregdatalistService.getByGnrlid(gnrlid);
        if (CollUtil.isNotEmpty(idregdatalistDtos)) {
            Element element = document.createElement("rsmi:idRegDataList");
            for (InstitutionsIdregdatalistDto idregdatalistDto : idregdatalistDtos) {
                Element idRegDataInfoElement = document.createElement("rsmi:idRegDataInfo");
                if (idregdatalistDto.getDeploymode() != null) {
                    Element deployModeElement = document.createElement("bt:deployMode");
                    deployModeElement.setTextContent(String.valueOf(idregdatalistDto.getDeploymode()));
                    idRegDataInfoElement.appendChild(deployModeElement);
                }
                if (idregdatalistDto.getName() != null) {
                    Element nameElement = document.createElement("bt:name");
                    nameElement.setTextContent(String.valueOf(idregdatalistDto.getName()));
                    idRegDataInfoElement.appendChild(nameElement);
                }
                if (idregdatalistDto.getAddress() != null) {
                    Element deployInfoElement = document.createElement("bt:deployInfo");
                    deployInfoElement.setAttribute("addrss", idregdatalistDto.getAddress());
                    deployInfoElement.setAttribute("city", idregdatalistDto.getCity());
                    deployInfoElement.setAttribute("county", idregdatalistDto.getCounty());
                    deployInfoElement.setAttribute("province", idregdatalistDto.getProvince());
                    idRegDataInfoElement.appendChild(deployInfoElement);
                }
                element.appendChild(idRegDataInfoElement);
            }
            dataElement.appendChild(element);
        }
    }

    private void writeXml(Document document, Date now, Element root, String timePath) {
        String fileName = PlatformTypeEnums.ZM.THIS_VALUE + "-" + currentNode.getGnrlId() +  "-" + PlatformTypeEnums.ZM.SMP.getCode()
                +  "-" + DateUtil.format(now, DatePattern.PURE_DATETIME_FORMAT) + RandomUtil.randomNumbers(5) + ".xml";
        document.appendChild(root);
        XmlUtils.writeXml(document, xmlPath + timePath, fileName);
    }

    /**
     * 校验
     */
    public void validateXML(String timePath) {
        log.info("**********************校验xml开始***********************");
        File[] ls = FileUtil.ls(xmlPath + timePath);
        for (File l : ls) {
            String xmlPath = l.getPath();
            File xsdFile = new File(xsdPath + "regSrvMainInfo.xsd");
            File xmlFile = new File(xmlPath);
            boolean validate = XmlUtils.validateXMLSchema(xsdFile, xmlFile);
            if (validate) {
                XmlUtils.signXml(xmlPath, currentNode.getPrivateKey());
            } else {
                // todo 校验失败处理
            }
        }
        log.info("**********************校验xml结束***********************");
    }

    /**
     * 打包
     */
    public void packetOrgXml(String timePath) {
        log.info("**********************打包xml开始***********************");
        File[] ls = FileUtil.ls(xmlPath + timePath);
        List<String> filePath = new ArrayList<>();
        for (File l : ls) {
            String xmlPath = l.getPath();
            filePath.add(xmlPath);
        }
        String fileName = PlatformTypeEnums.ZM.THIS_VALUE + "-" + currentNode.getGnrlId() +  "-" + PlatformTypeEnums.ZM.SMP.getCode()
                +  "-" + DateUtil.format(new Date(), DatePattern.PURE_DATETIME_FORMAT) + RandomUtil.randomNumbers(5) + ".tar.gz";
        XmlUtils.packetXml(tarPath + timePath, fileName, filePath);
        log.info("**********************打包xml结束***********************");
    }

    /**
     * 上传
     */
    public void uploadOrgXml(String timePath) {
        log.info("**********************上传xml开始***********************");
        SFtpUtil sFtpUtil = new SFtpUtil(sFtpProperties);
        File[] ls = FileUtil.ls(tarPath + timePath);
        log.info("tarPath:{}", tarPath + timePath);
        log.info("ls.length:{}", ls.length);
        for (File l : ls) {
            String path = l.getPath();
//            String uploadPath = currentNode.getXmlUploadDirectory() + PlatformTypeEnums.ZM.THIS_VALUE + "/" + sFtpProperties.getUsername() + "/"
//                    + PlatformTypeEnums.ZM.SMP.getCode() + "/"
//                    + DateUtil.format(new Date(), DatePattern.PURE_DATE_FORMAT) + "/" + l.getName();
            String uploadPath = "/" + PlatformTypeEnums.ZM.SMP.getCode() + "/"
                    + DateUtil.format(new Date(), DatePattern.PURE_DATE_FORMAT) + "/" + l.getName();
//            String uploadPath = l.getName();
            log.info("path:{}", path);
            log.info("uploadPath:{}", uploadPath);
            boolean upload = sFtpUtil.upload(path, uploadPath);
            log.info("上传标志:{}", upload);
        }
        log.info("**********************上传xml结束***********************");
    }

    public static void main(String[] args) {
//        new InstitutionsOrganizationService().validateXML();
        Date date = new Date();
        String timePath = DateUtil.format(date, DatePattern.PURE_DATE_FORMAT) + "/" + DateUtil.hour(date, true);
        System.out.println(timePath);
    }
}
